using Microsoft.AspNetCore.Authorization;
using Microsoft.AspNetCore.Mvc;
using Microsoft.EntityFrameworkCore;
using WeatherSystem.API.Data;
using WeatherSystem.API.Models;

namespace WeatherSystem.API.Controllers
{
    /// <summary>
    /// 城市管理控制器
    /// </summary>
    [ApiController]
    [Route("api/[controller]")]
    // [Authorize] // 已注释，后续可重新启用
    public class CityController : ControllerBase
    {
        private readonly WeatherDbContext _context;
        private readonly ILogger<CityController> _logger;

        public CityController(WeatherDbContext context, ILogger<CityController> logger)
        {
            _context = context;
            _logger = logger;
        }

        /// <summary>
        /// 获取城市列表（支持分页和筛选）
        /// </summary>
        [HttpGet]
        public async Task<ActionResult<PagedResult<object>>> GetAllCities(
            [FromQuery] int page = 1,
            [FromQuery] int pageSize = 20,
            [FromQuery] bool? isActive = null,
            [FromQuery] string? search = null,
            [FromQuery] string? country = null)
        {
            try
            {
                var query = _context.Cities.AsQueryable();

                // 状态筛选
                if (isActive.HasValue)
                {
                    query = query.Where(c => c.IsActive == isActive.Value);
                }

                // 搜索筛选
                if (!string.IsNullOrEmpty(search))
                {
                    query = query.Where(c => c.Name.Contains(search) || 
                                           c.Country.Contains(search));
                }

                // 国家筛选
                if (!string.IsNullOrEmpty(country))
                {
                    query = query.Where(c => c.Country.Contains(country));
                }

                var totalCount = await query.CountAsync();

                var cities = await query
                    .OrderBy(c => c.Country)
                    .ThenBy(c => c.Name)
                    .Skip((page - 1) * pageSize)
                    .Take(pageSize)
                    .AsNoTracking()
                    .Select(c => new
                    {
                        id = c.Id,
                        name = c.Name,
                        country = c.Country,
                        latitude = c.Latitude,
                        longitude = c.Longitude,
                        timeZone = c.TimeZone,
                        locationTechType = c.LocationTechType,
                        coordinateSystem = c.CoordinateSystem,
                        isActive = c.IsActive,
                        autoCollectEnabled = c.AutoCollectEnabled,
                        createdAt = c.CreatedAt
                    })
                    .ToListAsync();

                var result = new PagedResult<object>
                {
                    Data = cities.Cast<object>().ToList(),
                    TotalCount = totalCount,
                    Page = page,
                    PageSize = pageSize
                };

                return Ok(result);
            }
            catch (Exception ex)
            {
                _logger.LogError(ex, "获取城市列表失败");
                return StatusCode(500, new { message = "获取城市列表失败", error = ex.Message });
            }
        }

        /// <summary>
        /// 根据ID获取城市详情
        /// </summary>
        [HttpGet("{id}")]
        public async Task<ActionResult<City>> GetCity(Guid id)
        {
            try
            {
                var city = await _context.Cities.FindAsync(id);
                if (city == null)
                {
                    return NotFound(new { message = "城市不存在" });
                }

                return Ok(city);
            }
            catch (Exception ex)
            {
                _logger.LogError(ex, "获取城市详情失败，ID: {CityId}", id);
                return StatusCode(500, new { message = "获取城市详情失败", error = ex.Message });
            }
        }

        /// <summary>
        /// 添加新城市
        /// </summary>
        [HttpPost]
        public async Task<ActionResult<City>> CreateCity([FromBody] CreateCityRequest request)
        {
            try
            {
                // 验证城市名称是否已存在
                var existingCity = await _context.Cities
                    .FirstOrDefaultAsync(c => c.Name == request.Name && c.Country == request.Country);
                if (existingCity != null)
                {
                    return BadRequest(new { message = "该城市已存在" });
                }

                var city = new City
                {
                    Id = Guid.NewGuid(),
                    Name = request.Name,
                    Country = request.Country,
                    Latitude = request.Latitude,
                    Longitude = request.Longitude,
                    TimeZone = request.TimeZone,
                    IsActive = request.IsActive ?? true,
                    CreatedAt = DateTime.UtcNow
                };

                _context.Cities.Add(city);
                await _context.SaveChangesAsync();

                _logger.LogInformation("成功添加城市: {CityName}, ID: {CityId}", city.Name, city.Id);
                return CreatedAtAction(nameof(GetCity), new { id = city.Id }, city);
            }
            catch (Exception ex)
            {
                _logger.LogError(ex, "添加城市失败");
                return StatusCode(500, new { message = "添加城市失败", error = ex.Message });
            }
        }

        /// <summary>
        /// 更新城市信息
        /// </summary>
        [HttpPut("{id}")]
        public async Task<ActionResult<City>> UpdateCity(Guid id, [FromBody] UpdateCityRequest request)
        {
            try
            {
                var city = await _context.Cities.FindAsync(id);
                if (city == null)
                {
                    return NotFound(new { message = "城市不存在" });
                }

                // 检查是否有其他城市使用相同的名称和国家
                if (!string.IsNullOrEmpty(request.Name) || !string.IsNullOrEmpty(request.Country))
                {
                    var name = request.Name ?? city.Name;
                    var country = request.Country ?? city.Country;
                    
                    var existingCity = await _context.Cities
                        .FirstOrDefaultAsync(c => c.Id != id && c.Name == name && c.Country == country);
                    if (existingCity != null)
                    {
                        return BadRequest(new { message = "该城市名称已存在" });
                    }
                }

                // 更新字段
                if (!string.IsNullOrEmpty(request.Name)) city.Name = request.Name;
                if (!string.IsNullOrEmpty(request.Country)) city.Country = request.Country;
                if (request.Latitude.HasValue) city.Latitude = request.Latitude.Value;
                if (request.Longitude.HasValue) city.Longitude = request.Longitude.Value;
                if (!string.IsNullOrEmpty(request.TimeZone)) city.TimeZone = request.TimeZone;
                if (request.IsActive.HasValue) city.IsActive = request.IsActive.Value;

                await _context.SaveChangesAsync();

                _logger.LogInformation("成功更新城市: {CityName}, ID: {CityId}", city.Name, city.Id);
                return Ok(city);
            }
            catch (Exception ex)
            {
                _logger.LogError(ex, "更新城市失败，ID: {CityId}", id);
                return StatusCode(500, new { message = "更新城市失败", error = ex.Message });
            }
        }

        /// <summary>
        /// 删除城市
        /// </summary>
        [HttpDelete("{id}")]
        public async Task<ActionResult> DeleteCity(Guid id)
        {
            try
            {
                var city = await _context.Cities.FindAsync(id);
                if (city == null)
                {
                    return NotFound(new { message = "城市不存在" });
                }

                // 检查是否有关联的天气数据
                var hasWeatherData = await _context.WeatherDataEntries.AnyAsync(w => w.CityId == id);
                if (hasWeatherData)
                {
                    return BadRequest(new { message = "无法删除有天气数据记录的城市，请先删除相关数据或将城市设为禁用状态" });
                }

                _context.Cities.Remove(city);
                await _context.SaveChangesAsync();

                _logger.LogInformation("成功删除城市: {CityName}, ID: {CityId}", city.Name, city.Id);
                return NoContent();
            }
            catch (Exception ex)
            {
                _logger.LogError(ex, "删除城市失败，ID: {CityId}", id);
                return StatusCode(500, new { message = "删除城市失败", error = ex.Message });
            }
        }

        /// <summary>
        /// 切换城市状态（启用/禁用）
        /// </summary>
        [HttpPatch("{id}/toggle-status")]
        public async Task<ActionResult<City>> ToggleCityStatus(Guid id)
        {
            try
            {
                var city = await _context.Cities.FindAsync(id);
                if (city == null)
                {
                    return NotFound(new { message = "城市不存在" });
                }

                city.IsActive = !city.IsActive;

                await _context.SaveChangesAsync();

                _logger.LogInformation("成功切换城市状态: {CityName}, ID: {CityId}, 新状态: {Status}", 
                    city.Name, city.Id, city.IsActive ? "启用" : "禁用");
                
                return Ok(city);
            }
            catch (Exception ex)
            {
                _logger.LogError(ex, "切换城市状态失败，ID: {CityId}", id);
                return StatusCode(500, new { message = "切换城市状态失败", error = ex.Message });
            }
        }

        /// <summary>
        /// 批量更新城市状态
        /// </summary>
        [HttpPatch("batch-status")]
        public async Task<ActionResult> BatchUpdateCityStatus([FromBody] BatchUpdateStatusRequest request)
        {
            try
            {
                if (request.CityIds == null || !request.CityIds.Any())
                {
                    return BadRequest(new { message = "城市ID列表不能为空" });
                }

                var cities = await _context.Cities
                    .Where(c => request.CityIds.Contains(c.Id))
                    .ToListAsync();

                if (!cities.Any())
                {
                    return NotFound(new { message = "未找到指定的城市" });
                }

                foreach (var city in cities)
                {
                    city.IsActive = request.IsActive;
                }

                await _context.SaveChangesAsync();

                _logger.LogInformation("批量更新城市状态成功，影响 {Count} 个城市，新状态: {Status}", 
                    cities.Count, request.IsActive ? "启用" : "禁用");
                
                return Ok(new { message = $"成功更新 {cities.Count} 个城市的状态", updatedCount = cities.Count });
            }
            catch (Exception ex)
            {
                _logger.LogError(ex, "批量更新城市状态失败");
                return StatusCode(500, new { message = "批量更新城市状态失败", error = ex.Message });
            }
        }

        /// <summary>
        /// 切换城市自动采集状态
        /// </summary>
        [HttpPatch("{id}/toggle-auto-collect")]
        public async Task<ActionResult<City>> ToggleCityAutoCollect(Guid id)
        {
            try
            {
                var city = await _context.Cities.FindAsync(id);
                if (city == null)
                {
                    return NotFound(new { message = "城市不存在" });
                }

                city.AutoCollectEnabled = !city.AutoCollectEnabled;

                await _context.SaveChangesAsync();

                _logger.LogInformation("成功切换城市自动采集状态: {CityName}, ID: {CityId}, 新状态: {Status}", 
                    city.Name, city.Id, city.AutoCollectEnabled ? "启用" : "禁用");
                
                return Ok(city);
            }
            catch (Exception ex)
            {
                _logger.LogError(ex, "切换城市自动采集状态失败，ID: {CityId}", id);
                return StatusCode(500, new { message = "切换城市自动采集状态失败", error = ex.Message });
            }
        }

        /// <summary>
        /// 批量更新城市自动采集状态
        /// </summary>
        [HttpPatch("batch-auto-collect")]
        public async Task<ActionResult> BatchUpdateCityAutoCollect([FromBody] BatchUpdateAutoCollectRequest request)
        {
            try
            {
                if (request.CityIds == null || !request.CityIds.Any())
                {
                    return BadRequest(new { message = "城市ID列表不能为空" });
                }

                var cities = await _context.Cities
                    .Where(c => request.CityIds.Contains(c.Id))
                    .ToListAsync();

                if (!cities.Any())
                {
                    return NotFound(new { message = "未找到指定的城市" });
                }

                foreach (var city in cities)
                {
                    city.AutoCollectEnabled = request.AutoCollectEnabled;
                }

                await _context.SaveChangesAsync();

                _logger.LogInformation("批量更新城市自动采集状态成功，影响 {Count} 个城市，新状态: {Status}", 
                    cities.Count, request.AutoCollectEnabled ? "启用" : "禁用");
                
                return Ok(new { message = $"成功更新 {cities.Count} 个城市的自动采集状态", updatedCount = cities.Count });
            }
            catch (Exception ex)
            {
                _logger.LogError(ex, "批量更新城市自动采集状态失败");
                return StatusCode(500, new { message = "批量更新城市自动采集状态失败", error = ex.Message });
            }
        }
    }

    // 请求模型
    public class CreateCityRequest
    {
        public string Name { get; set; } = string.Empty;
        public string Country { get; set; } = string.Empty;
        public decimal Latitude { get; set; }
        public decimal Longitude { get; set; }
        public string TimeZone { get; set; } = string.Empty;
        public bool? IsActive { get; set; }
    }

    public class UpdateCityRequest
    {
        public string? Name { get; set; }
        public string? Country { get; set; }
        public decimal? Latitude { get; set; }
        public decimal? Longitude { get; set; }
        public string? TimeZone { get; set; }
        public bool? IsActive { get; set; }
    }

    public class BatchUpdateStatusRequest
    {
        public List<Guid> CityIds { get; set; } = new();
        public bool IsActive { get; set; }
    }

    public class BatchUpdateAutoCollectRequest
    {
        public List<Guid> CityIds { get; set; } = new();
        public bool AutoCollectEnabled { get; set; }
    }
}